<script setup>
import { ref, onMounted } from 'vue'
import { get, post, put, del, uploadFile, downloadFile } from '../utils/request'

// 用户列表数据
const users = ref([])
// 加载状态
const loading = ref(false)
// 错误信息
const error = ref(null)
// 操作消息
const message = ref('')
const messageType = ref('success')
const showMessage = ref(false)

// 新用户表单
const newUser = ref({
  name: '',
  email: '',
  avatar: null
})

// 获取用户列表
async function fetchUsers() {
  loading.value = true
  error.value = null
  
  try {
    const response = await get('/users')
    users.value = response
    showNotification('获取用户列表成功', 'success')
  } catch (err) {
    error.value = err.message
    showNotification('获取用户列表失败', 'error')
  } finally {
    loading.value = false
  }
}

// 创建用户
async function createUser() {
  if (!newUser.value.name || !newUser.value.email) {
    showNotification('请填写完整的用户信息', 'error')
    return
  }
  
  loading.value = true
  
  try {
    const formData = new FormData()
    formData.append('name', newUser.value.name)
    formData.append('email', newUser.value.email)
    if (newUser.value.avatar) {
      formData.append('avatar', newUser.value.avatar)
    }
    
    await post('/users', formData, {
      headers: {
        'Content-Type': 'multipart/form-data'
      }
    })
    
    showNotification('创建用户成功', 'success')
    resetForm()
    fetchUsers()
  } catch (err) {
    showNotification('创建用户失败', 'error')
  } finally {
    loading.value = false
  }
}

// 更新用户
async function updateUser(userId, userData) {
  loading.value = true
  
  try {
    await put(`/users/${userId}`, userData)
    showNotification('更新用户成功', 'success')
    fetchUsers()
  } catch (err) {
    showNotification('更新用户失败', 'error')
  } finally {
    loading.value = false
  }
}

// 删除用户
async function deleteUser(userId) {
  if (!confirm('确定要删除此用户吗？')) {
    return
  }
  
  loading.value = true
  
  try {
    await del(`/users/${userId}`)
    showNotification('删除用户成功', 'success')
    fetchUsers()
  } catch (err) {
    showNotification('删除用户失败', 'error')
  } finally {
    loading.value = false
  }
}

// 上传头像
async function handleAvatarUpload(event) {
  const file = event.target.files[0]
  if (!file) return
  
  try {
    const response = await uploadFile('/upload', file)
    newUser.value.avatar = response.url
    showNotification('头像上传成功', 'success')
  } catch (err) {
    showNotification('头像上传失败', 'error')
  }
}

// 下载文件
async function handleDownload(filename) {
  try {
    await downloadFile('/download', { filename }, filename)
    showNotification('文件下载成功', 'success')
  } catch (err) {
    showNotification('文件下载失败', 'error')
  }
}

// 重置表单
function resetForm() {
  newUser.value = {
    name: '',
    email: '',
    avatar: null
  }
}

// 显示通知
function showNotification(msg, type = 'success') {
  message.value = msg
  messageType.value = type
  showMessage.value = true
  
  setTimeout(() => {
    showMessage.value = false
  }, 3000)
}

// 组件挂载时获取用户列表
onMounted(() => {
  fetchUsers()
})
</script>

<template>
  <div class="tutorial-container">
    <header>
      <h1>07.Axios 教程</h1>
      <p class="subtitle">学习如何在Vue中使用Axios进行HTTP请求</p>
    </header>

    <main>
      <section class="intro">
        <h2>Axios 基础使用</h2>
        <p>Axios是一个基于Promise的HTTP客户端，用于浏览器和node.js。它具有以下特点：</p>
        <ul>
          <li>支持Promise API</li>
          <li>拦截请求和响应</li>
          <li>转换请求和响应数据</li>
          <li>自动转换JSON数据</li>
          <li>客户端支持防御XSRF</li>
        </ul>
      </section>

      <div class="demo-section">
        <!-- 通知消息 -->
        <div v-if="showMessage" :class="['notification', messageType]">
          {{ message }}
        </div>

        <!-- 用户管理表单 -->
        <div class="card">
          <h3>添加新用户</h3>
          <div class="form">
            <div class="form-group">
              <label>用户名</label>
              <input v-model="newUser.name" type="text" placeholder="请输入用户名" />
            </div>
            
            <div class="form-group">
              <label>邮箱</label>
              <input v-model="newUser.email" type="email" placeholder="请输入邮箱" />
            </div>
            
            <div class="form-group">
              <label>头像</label>
              <input type="file" @change="handleAvatarUpload" accept="image/*" />
            </div>
            
            <button @click="createUser" class="btn primary" :disabled="loading">
              {{ loading ? '提交中...' : '创建用户' }}
            </button>
          </div>
        </div>

        <!-- 用户列表 -->
        <div class="card">
          <h3>用户列表</h3>
          
          <div v-if="loading" class="loading">
            <div class="spinner"></div>
            <p>加载中...</p>
          </div>
          
          <div v-else-if="error" class="error">
            <p>{{ error }}</p>
            <button @click="fetchUsers" class="btn primary">重试</button>
          </div>
          
          <div v-else class="users-list">
            <div v-for="user in users" :key="user.id" class="user-item">
              <div class="user-info">
                <img :src="user.avatar" :alt="user.name" class="avatar" />
                <div>
                  <h4>{{ user.name }}</h4>
                  <p>{{ user.email }}</p>
                </div>
              </div>
              
              <div class="user-actions">
                <button @click="updateUser(user.id, { ...user, name: user.name + ' (已更新)' })" 
                        class="btn secondary small">
                  更新
                </button>
                <button @click="deleteUser(user.id)" class="btn danger small">删除</button>
              </div>
            </div>
          </div>
        </div>
      </div>

      <section class="explanation">
        <h2>Axios 使用详解</h2>
        
        <div class="subsection">
          <h3>1. 基本请求方法</h3>
          <div class="code-example">
            <pre><code>// GET请求
axios.get('/api/users')
  .then(response => {
    console.log(response.data)
  })
  .catch(error => {
    console.error(error)
  })

// POST请求
axios.post('/api/users', {
  name: 'John',
  email: 'john@example.com'
})
  .then(response => {
    console.log(response.data)
  })
  .catch(error => {
    console.error(error)
  })</code></pre>
          </div>
        </div>
        
        <div class="subsection">
          <h3>2. 请求配置</h3>
          <div class="code-example">
            <pre><code>// 创建实例
const instance = axios.create({
  baseURL: 'https://api.example.com',
  timeout: 5000,
  headers: {
    'Content-Type': 'application/json'
  }
})

// 使用实例
instance.get('/users')
  .then(response => {
    console.log(response.data)
  })</code></pre>
          </div>
        </div>
        
        <div class="subsection">
          <h3>3. 拦截器</h3>
          <div class="code-example">
            <pre><code>// 请求拦截器
axios.interceptors.request.use(
  config => {
    // 在发送请求之前做些什么
    const token = localStorage.getItem('token')
    if (token) {
      config.headers.Authorization = `Bearer ${token}`
    }
    return config
  },
  error => {
    return Promise.reject(error)
  }
)

// 响应拦截器
axios.interceptors.response.use(
  response => {
    // 对响应数据做点什么
    return response.data
  },
  error => {
    // 对响应错误做点什么
    return Promise.reject(error)
  }
)</code></pre>
          </div>
        </div>
        
        <div class="subsection">
          <h3>4. 错误处理</h3>
          <div class="code-example">
            <pre><code>axios.get('/api/users')
  .then(response => {
    console.log(response.data)
  })
  .catch(error => {
    if (error.response) {
      // 服务器返回了错误状态码
      console.error('错误状态码:', error.response.status)
      console.error('错误数据:', error.response.data)
    } else if (error.request) {
      // 请求已发送但没有收到响应
      console.error('未收到响应:', error.request)
    } else {
      // 请求配置出错
      console.error('请求错误:', error.message)
    }
  })</code></pre>
          </div>
        </div>
      </section>
    </main>
  </div>
</template>

<style scoped>
.tutorial-container {
  max-width: 1200px;
  margin: 0 auto;
  padding: 20px;
}

header {
  margin-bottom: 30px;
  border-bottom: 1px solid #eee;
  padding-bottom: 20px;
}

h1 {
  font-size: 2.5rem;
  margin-bottom: 10px;
}

.subtitle {
  font-size: 1.2rem;
  color: #666;
  margin-bottom: 20px;
}

.intro {
  margin-bottom: 40px;
}

.code-example {
  background-color: #f8f8f8;
  border-radius: 6px;
  padding: 15px;
  margin: 15px 0;
  overflow-x: auto;
}

pre {
  margin: 0;
}

code {
  font-family: 'Courier New', monospace;
  font-size: 0.9rem;
}

.demo-section {
  margin-bottom: 40px;
}

.card {
  background-color: white;
  border-radius: 8px;
  box-shadow: 0 2px 8px rgba(0, 0, 0, 0.1);
  padding: 20px;
  margin-bottom: 20px;
}

.form {
  max-width: 500px;
}

.form-group {
  margin-bottom: 15px;
}

label {
  display: block;
  margin-bottom: 5px;
  font-weight: 500;
}

input {
  width: 100%;
  padding: 8px 12px;
  border: 1px solid #ddd;
  border-radius: 4px;
  font-size: 1rem;
}

.btn {
  padding: 8px 16px;
  border: none;
  border-radius: 4px;
  cursor: pointer;
  font-size: 1rem;
  transition: background-color 0.2s;
}

.btn.primary {
  background-color: #4CAF50;
  color: white;
}

.btn.primary:hover {
  background-color: #3e8e41;
}

.btn.secondary {
  background-color: #f1f1f1;
  color: #333;
}

.btn.secondary:hover {
  background-color: #e0e0e0;
}

.btn.danger {
  background-color: #f44336;
  color: white;
}

.btn.danger:hover {
  background-color: #d32f2f;
}

.btn.small {
  padding: 4px 8px;
  font-size: 0.9rem;
}

.btn:disabled {
  background-color: #cccccc;
  cursor: not-allowed;
}

.notification {
  padding: 10px 15px;
  border-radius: 4px;
  margin-bottom: 20px;
}

.notification.success {
  background-color: #dff0d8;
  color: #3c763d;
  border: 1px solid #d6e9c6;
}

.notification.error {
  background-color: #f2dede;
  color: #a94442;
  border: 1px solid #ebccd1;
}

.loading {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  padding: 30px 0;
}

.spinner {
  width: 40px;
  height: 40px;
  border: 4px solid #f3f3f3;
  border-top: 4px solid #4CAF50;
  border-radius: 50%;
  animation: spin 1s linear infinite;
  margin-bottom: 10px;
}

@keyframes spin {
  0% { transform: rotate(0deg); }
  100% { transform: rotate(360deg); }
}

.error {
  text-align: center;
  padding: 20px;
  color: #a94442;
}

.users-list {
  display: grid;
  gap: 15px;
}

.user-item {
  display: flex;
  justify-content: space-between;
  align-items: center;
  padding: 15px;
  border: 1px solid #eee;
  border-radius: 6px;
}

.user-info {
  display: flex;
  align-items: center;
  gap: 15px;
}

.avatar {
  width: 50px;
  height: 50px;
  border-radius: 50%;
  object-fit: cover;
}

.user-actions {
  display: flex;
  gap: 10px;
}

.explanation {
  margin-top: 40px;
}

.subsection {
  margin-bottom: 30px;
}
</style> 